/*
 *  HumanPlayer.cpp
 *  RiskAI
 *
 *  The Human Player makes descisions by prompting the user to cin a variable.
 *  
 *  NOTE: As of yet, there is no input checking, so BE CAREFUL.
 *
 */

#include "HumanPlayer.h"

#include <iostream>
#include <vector>

using namespace std;




//**********************************************************************************
//				CONSTRUCTION
//**********************************************************************************

CHumanPlayer::CHumanPlayer(int iIndex, CBoard* pxBoard)
	: CPlayer(iIndex, pxBoard)
{
}




//**********************************************************************************
//				HELPER FUNCTIONS
//**********************************************************************************

int
CHumanPlayer::GetTerritory(std::vector<int> viChoices)
{
	cout << endl << "You can choose one of the following Territories:";
	
	for(unsigned int i=0; i<viChoices.size(); i++)
		cout << " " << viChoices[i];
	
	cout << endl << "Pick one: ";
	
	int iChoice;
	cin >> iChoice;
	cout << endl;
	return iChoice;
}





//**********************************************************************************
//				VIRTUAL FUNCTIONS
//**********************************************************************************

int
CHumanPlayer::PickTerritory(vector<int> viAvailables)
{
	m_pxBoard->PrintBoardState();
	cout << "Player " << m_iIndex << "\'s turn. ";
	return GetTerritory(viAvailables);
}

//==================================================================================

int
CHumanPlayer::AssignTroops(int iNumTroops)
{
	cout << "Player " << m_iIndex << ", you have " << iNumTroops << " troops left to place.";
	m_pxBoard->PrintBoardState();
	return GetTerritory(m_viTerritories);
}

//==================================================================================

int
CHumanPlayer::MoveTroops(int iSourceIndex, int iDestinationIndex)
{
	int iMaxTroops = m_pxBoard->GetTerritory(iSourceIndex)->GetNumArmies() - 1;
	if(iMaxTroops == 0) return 0;
	
	cout << "Player " << m_iIndex << " can move troops from " << iSourceIndex
		 << " to " << iDestinationIndex << endl;
	cout << m_pxBoard->GetTerritoryInfo(iSourceIndex) << endl;
	cout << m_pxBoard->GetTerritoryInfo(iDestinationIndex) << endl;
	
	cout << "How many would you like to move? (Up to " << iMaxTroops << "): ";
	
	int iTroops;
	cin >> iTroops;
	cout << endl;
	
	return iTroops;
}

//==================================================================================

RiskAction
CHumanPlayer::DecideOnAction(vector<int> viViableAttackers)
{
	cout << endl << "Player " << m_iIndex << ", choose a Territory to attack from (-1 to end turn): ";
	int iSource = GetTerritory(viViableAttackers);
	if(iSource == -1) return END_TURN;
	
	vector<int> viBorders = m_pxBoard->GetTerritory(iSource)->GetBorderIndices();
	
	for(unsigned int i=viBorders.size(); i>0; i--)
	{
		int iOwner = m_pxBoard->GetTerritory(viBorders[i-1])->GetOwner();
		if(iOwner == m_iIndex)
		{
			viBorders.erase(viBorders.begin() + (i-1));
		}
	}
	
	cout << "Now choose a territory to attack: ";
	int iTarget = GetTerritory(viBorders);
	
	int iMaxDice = m_pxBoard->GetTerritory(iSource)->GetNumArmies() - 1;
	if(iMaxDice > 3) iMaxDice = 3;
	
	cout << "How many dice will you roll? (you can roll up to " << iMaxDice << "): ";
	int iDice;
	cin >> iDice;
	
	return RiskAction(iSource, iTarget, iDice);
}

//==================================================================================

int
CHumanPlayer::PickDefendingDie(int* aiAttackDice, int iTarget)
{
	int iMaxDice = m_pxBoard->GetTerritory(iTarget)->GetNumArmies();
	if(iMaxDice > 2) iMaxDice = 2;
	
	cout << "Player " << m_iIndex << ", choose how many dice to defend with (you may use up to "
		 << iMaxDice << "): ";
	int iNumDice;
	cin >> iNumDice;
	
	return iNumDice;
}

//==================================================================================

CFortification
CHumanPlayer::FortifyTroops(vector<int> viFortifiers)
{
	cout << endl << "Player " << m_iIndex << ", choose a Territory to fortify Troops from (-1 for none):" << endl;
	int iSource = GetTerritory(viFortifiers);
	if(iSource == -1) return NO_FORTIFICATION;
	
	vector<int> viBorders = m_pxBoard->GetTerritory(iSource)->GetBorderIndices();
	
	for(unsigned int i=viBorders.size(); i>0; i--)
	{
		int iOwner = m_pxBoard->GetTerritory(viBorders[i-1])->GetOwner();
		if(iOwner != m_iIndex)
		{
			viBorders.erase(viBorders.begin() + (i-1));
		}
	}
	
	cout << "Now choose a Territory to move troops into:";
	int iTarget = GetTerritory(viBorders);
	
	cout << m_pxBoard->GetTerritoryInfo(iSource) << endl;
	cout << m_pxBoard->GetTerritoryInfo(iTarget) << endl;
	
	int iMaxTroops = m_pxBoard->GetTerritory(iSource)->GetNumArmies() - 1;
	cout << "Choose how many to move (up to " << iMaxTroops << "): ";
	
	int iTroops;
	cin >> iTroops;
	
	return CFortification(iSource, iTarget, iTroops);
}